using Headspring.Training.Core.Model;
using Headspring.Training.Core.Model.StateCommands;
using Headspring.Training.Core.Services;
using NUnit.Framework;
using NUnit.Framework.SyntaxHelpers;
using Rhino.Mocks;

namespace Headspring.Training.UnitTests.Model.StateCommands
{
	[TestFixture]
	public class InProgressToAssignedCommandTester
	{
		[Test]
		public void ShouldHaveCorrectVerbs()
		{
			var command = new InProgressToAssignedCommand(null, null);
			Assert.That(command.TransitionVerbPastTense, Is.EqualTo("Shelved"));
			Assert.That(command.TransitionVerbPresentTense, Is.EqualTo("Shelve"));
		}

		[Test]
		public void ShouldBeValid()
		{
			var order = new WorkOrder {Status = WorkOrderStatus.InProgress};
			var employee = new Employee();
			order.Assignee = employee;

			var command = new InProgressToAssignedCommand(order, employee);
			Assert.That(command.IsValid(), Is.True);
		}

		[Test]
		public void ShouldNotBeValidInWrongStatus()
		{
			var order = new WorkOrder {Status = WorkOrderStatus.Draft};
			var employee = new Employee();
			order.Assignee = employee;

			var command = new InProgressToAssignedCommand(order, employee);
			Assert.That(command.IsValid(), Is.False);
		}

		[Test]
		public void ShouldNotBeValidWithWrongEmployee()
		{
			var order = new WorkOrder {Status = WorkOrderStatus.InProgress};
			var employee = new Employee();
			order.Assignee = employee;

			var command = new InProgressToAssignedCommand(order, new Employee());
			Assert.That(command.IsValid(), Is.False);
		}

		[Test]
		public void ShouldTransitionStateFromInProgressToCancelled()
		{
			var order = new WorkOrder
			            	{Number = "123", Status = WorkOrderStatus.InProgress};
			var employee = new Employee();
			order.Assignee = employee;

			var commandVisitor = MockRepository.GenerateMock<IStateCommandVisitor>();
			commandVisitor.Expect(visitor => visitor.SaveWorkOrder(order));
			commandVisitor.Expect(
				visitor => visitor.SendMessage("You have shelved work order 123"));
			commandVisitor.Expect(visitor => visitor.EditWorkOrder(order));

			var command = new InProgressToAssignedCommand(order, employee);
			command.Execute(commandVisitor);

			commandVisitor.VerifyAllExpectations();
			Assert.That(order.Status, Is.EqualTo(WorkOrderStatus.Assigned));
		}
	}
}